package rgroupinterceptor

import (
	"context"
	"encoding/json"
	"github.com/go-playground/validator"
	"strconv"
	"time"
	"vpn-management-server/logger"
	"vpn-management-server/network"
	"vpn-management-server/security/code"
	"vpn-management-server/src/model/adminlogmodel"
	"vpn-management-server/src/model/adminmodel"
	"vpn-management-server/src/model/rgroupmodel"
	"vpn-management-server/src/service/adminlogservice"
	"vpn-management-server/src/service/adminservice"
)

// AddRGroupValidator
// @Title AddRGroupValidator
// @Description 添加规则组验证器
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func AddRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var RGroup rgroupmodel.RGroup
	err := json.Unmarshal(request.Parameters, &RGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to RGroup error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(RGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 验证管理员权限 只有超级管理员、规则管理员和用户组管理员可以添加规则组
	// TODO 但是需要注意的是 用户组管理员添加的规则组需要加上ug_id即属于的用户组ID 另外两种管理员这个字段设置为-1
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&RGroup)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GetRGroupValidator
// @Title GetRGroupValidator
// @Description 分页获取规则组验证器
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GetRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var RGroupGet rgroupmodel.GetRGroup
	err := json.Unmarshal([]byte(request.Parameters), &RGroupGet)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to GetRGroup error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(RGroupGet)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 验证管理员权限 只有超级管理员、规则管理员和用户组管理员可以 查看用户组规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&RGroupGet)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// DeleteRGroupValidator
// @Title DeleteRGroupValidator
// @Description 删除规则组
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DeleteRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var RGroupInfo rgroupmodel.RGroupInfo
	err := json.Unmarshal(request.Parameters, &RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to RGroupInfo error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 三种管理员都可以删除规则组 删除的规则组有所不同
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin {
		request.SetModel(&RGroupInfo)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GrantRGroupToUGroupValidator
// @Title GrantRGroupToUGroupValidator
// @Description 授权用户组验证器
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GrantRGroupToUGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var GrantUGroup rgroupmodel.GrantUGroup
	err := json.Unmarshal([]byte(request.Parameters), &GrantUGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to GrantUGroup error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(GrantUGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 规则管理员和超级管理员可以授予规则组给用户组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&GrantUGroup)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// DepriveRGroupFromUGroupValidator
// @Title DepriveRGroupFromUGroupValidator
// @Description 在用户组中删除规则组 仅限于用户组管理员 用户组管理员可以使用超级/规则管理员分配的规则/规则组创建新的规则组
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DepriveRGroupFromUGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var deprive rgroupmodel.DepriveUGroup
	err := json.Unmarshal(request.Parameters, &deprive)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to DepriveUGroup error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(deprive)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 超级管理员或规则管理员有权限剥夺用户组规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin {
		request.SetModel(&deprive)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// DeleteUGroupRGroupValidator
// @Title DeleteUGroupRGroupValidator
// @Description 用户组管理员删除用户组规则组
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DeleteUGroupRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var RGroupInfo rgroupmodel.RGroupInfo
	err := json.Unmarshal(request.Parameters, &RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to RGroupInfo error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 只有用户组管理员可以删除用户组中的规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.UserGroupAdmin {
		request.SetModel(&RGroupInfo)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GrantRGroupToUserValidator
// @Title GrantRGroupToUserValidator
// @Description 用户组管理员分配规则组到用户验证器
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GrantRGroupToUserValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var GrantUser rgroupmodel.GrantUser
	err := json.Unmarshal(request.Parameters, &GrantUser)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to GrantUser error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(GrantUser)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 只有用户组管理员能分配用户组的规则组给用户
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.UserGroupAdmin {
		request.SetModel(&GrantUser)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// DepriveRGroupFromUserValidator
// @Title DepriveRGroupFromUserValidator
// @Description 用户组管理员剥夺分配给用户的规则组
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DepriveRGroupFromUserValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var deprive rgroupmodel.DepriveUser
	err := json.Unmarshal(request.Parameters, &deprive)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to DepriveUser error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(deprive)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 只有用户组管理员能剥夺用户的规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.UserGroupAdmin {
		request.SetModel(&deprive)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GrantRuleToRGroupValidator
// @Title GrantRuleToRGroupValidator
// @Description 管理员授予规则给规则组
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GrantRuleToRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var GrantRule rgroupmodel.GrantRule
	err := json.Unmarshal(request.Parameters, &GrantRule)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to GrantRule error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(GrantRule)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 三种管理员都可以分配规则给规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&GrantRule)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// DepriveRuleFromRGroupValidator
// @Title DepriveRuleFromRGroupValidator
// @Description 管理员剥夺规则组的规则
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DepriveRuleFromRGroupValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var DepriveRule rgroupmodel.DepriveRule
	err := json.Unmarshal(request.Parameters, &DepriveRule)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to DepriveUser error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(DepriveRule)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// TODO 三种管理员都可以剥夺规则组中的规则
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&DepriveRule)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GetRGroupRuleInfosValidator
// @Title GetRGroupRuleInfosValidator
// @Description 根据规则组ID获取规则组中的规则信息（ID+Name）
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GetRGroupRuleInfosValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var RGroupInfo rgroupmodel.RGroupInfo
	err := json.Unmarshal(request.Parameters, &RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to RGroupInfo error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(RGroupInfo)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// 三种管理员都可以获取规则组中的规则信息
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.SuperAdmin || rank == adminmodel.RuleAdmin || rank == adminmodel.UserGroupAdmin {
		request.SetModel(&RGroupInfo)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// GetUserRGroupByPageValidator
// @Title GetUserRGroupByPageValidator
// @Description 分页获取用户所拥有的规则组验证器
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func GetUserRGroupByPageValidator(ctx context.Context, request *network.NetRequest, response *network.NetResponse) bool {
	var GetUserRGroup rgroupmodel.GetUserRGroup
	err := json.Unmarshal(request.Parameters, &GetUserRGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "UnMarshal Parameters to RGroupInfo error,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "parse parameters fail"
		return false
	}
	valid := validator.New()
	err = valid.Struct(GetUserRGroup)
	if err != nil {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "validate Parameters fail,", err)
		response.Code = code.BAD_REQUEST
		response.ErrorMsg = "validate parameters fail"
		return false
	}
	// 只有用户组管理员可以获取用户的规则组
	if rank := adminservice.GetAdminRankService(ctx, request, response); rank == adminmodel.UserGroupAdmin {
		request.SetModel(&GetUserRGroup)
		return true
	} else {
		logger.Logger.ErrorWithConn(ctx.Value("conn_id").(string), "have no authority")
		response.Code = code.UNAUTHORIZED
		response.ErrorMsg = "have no authority"
		return false
	}
}

// AddRGroupLogToChan
// @Title AddRGroupLogToChan
// @Description 添加规则组日志
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func AddRGroupLogToChan(ctx context.Context, request *network.NetRequest, response *network.NetResponse) {
	RGroup := request.GetModel().(*rgroupmodel.RGroup)
	adminlogservice.AddAdminLogToChan(adminlogservice.ChanAdminLogs, adminlogmodel.AdminLog{
		Name:      adminservice.GetCurrAdminService(ctx, request, response).Name,
		Source:    request.GetRemote(),
		Location:  "地址",
		Behavior:  "添加规则组：" + RGroup.Name,
		TimeStamp: strconv.FormatInt(time.Now().Unix(), 10),
	})
}

// DeleteRGroupsLogToChan
// @Title DeleteRGroupsLogToChan
// @Description 删除规则组日志
// @Param ctx context.Context
// @Param request *network.NetRequest
// @Param response *network.NetResponse
func DeleteRGroupsLogToChan(ctx context.Context, request *network.NetRequest, response *network.NetResponse) {
	RGroupInfo := request.GetModel().(*rgroupmodel.RGroupInfo)
	adminlogservice.AddAdminLogToChan(adminlogservice.ChanAdminLogs, adminlogmodel.AdminLog{
		Name:      adminservice.GetCurrAdminService(ctx, request, response).Name,
		Source:    request.GetRemote(),
		Location:  "地址",
		Behavior:  "删除规则组：" + RGroupInfo.Name,
		TimeStamp: strconv.FormatInt(time.Now().Unix(), 10),
	})
}
